package com.sh169.action.admin;

import java.io.File;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.Random;

import javax.servlet.http.HttpServletRequest;

import org.nutz.dao.Cnd;
import org.nutz.dao.Dao;
import org.nutz.dao.pager.Pager;
import org.nutz.ioc.annotation.InjectName;
import org.nutz.ioc.loader.annotation.Inject;
import org.nutz.ioc.loader.annotation.IocBean;
import org.nutz.lang.Files;
import org.nutz.lang.Strings;
import org.nutz.lang.random.StringGenerator;
import org.nutz.log.Log;
import org.nutz.log.Logs;
import org.nutz.mvc.annotation.AdaptBy;
import org.nutz.mvc.annotation.At;
import org.nutz.mvc.annotation.Ok;
import org.nutz.mvc.annotation.Param;
import org.nutz.mvc.upload.UploadAdaptor;
import org.nutz.trans.Atom;
import org.nutz.trans.Trans;

import com.sh169.action.user.VendorHomeAction;
import com.sh169.actionform.ProductForm;
import com.sh169.actionform.UserForm;
import com.sh169.beans.PageForm;
import com.sh169.pojos.Article;
import com.sh169.pojos.Brand;
import com.sh169.pojos.Classify;
import com.sh169.pojos.NewsImage;
import com.sh169.pojos.Pinpai;
import com.sh169.pojos.Product;
import com.sh169.pojos.Role;
import com.sh169.pojos.RoleUserRelation;
import com.sh169.pojos.SpecialVendor;
import com.sh169.pojos.User;
import com.sh169.pojos.Vendor;
import com.sh169.service.auth.AuthHomeService;
import com.sh169.util.ApplicationUtil;
import com.sh169.util.FreemarkerUtils;
import com.sh169.util.Md5;

@At("/admin")
@IocBean(name="adminHomeAction")
@InjectName("adminHomeAction")
public class HomeAction {
	private static final Log log = Logs.getLog(HomeAction.class);
	@Inject("refer:authHomeService")
	private AuthHomeService authHomeService;
	@Inject("refer:dao")
	private Dao dao;
	public Dao getDao() {
		return dao;
	}
	public void setDao(Dao dao) {
		this.dao = dao;
	}
	public AuthHomeService getAuthHomeService() {
		return authHomeService;
	}
	public void setAuthHomeService(AuthHomeService authHomeService) {
		this.authHomeService = authHomeService;
	}
	@At("/user/manage")
	@Ok("tiles:admin.user.manage")
	public List<User> userManage(){
		List<User> users = dao.query(User.class,null,null);
		return users;
	}
	/**
	 * 只更新需要更新的字段就可以
	 * @param user
	 * @param ids
	 */
	@At("/user/update")
	@Ok("redirect:/admin/user/manage")
	public void userUpdate(@Param("::user.") final User user,@Param("ids") final String[] ids){
		Trans.exec(new Atom(){
			public void run() {
				if(user==null || Strings.isEmpty(user.getId()+"")) return;
				User temp = dao.fetch(User.class,user.getId()) ;
				dao.clear(RoleUserRelation.class,Cnd.where("userid","=",user.getId()));
				temp.setAddress(user.getAddress());
				temp.setNickName(user.getNickName());
				temp.setPhone(user.getPhone());
				temp.setTelephone(user.getTelephone());
				temp.setState(user.getState());
				if(!Strings.isEmpty(user.getPassword()))
					temp.setPassword(Md5.encode(temp.getUsername()+user.getPassword()));
				dao.update(temp);
				if(ids!= null && ids.length>0){
					for(String id: ids){
						RoleUserRelation rur = new RoleUserRelation();
						rur.setRoleid(id);
						rur.setUserid(user.getId());
						dao.fastInsert(rur);
					}
				}
			}
		});
	}
	@At("/user/preupdate")
	@Ok("tiles:admin.user.preupdate")
	public UserForm userPreUpdate(@Param("userid")long userid){
		User user = dao.fetch(User.class,userid);
		dao.fetchLinks(user, "roles");
		UserForm uf = new UserForm();
		uf.setUser(user);
		List<Role> roles = dao.query(Role.class, null, null);
		uf.setRoles(roles);
		return uf;
	}
	@At("/role/manage")
	@Ok("tiles:admin.role.manage")
	public List<Role> roleManage(){
		List<Role> roles = dao.query(Role.class,null,null);
		return roles;
	}
	@At({"/role/preadd","/role/preupdate"})
	@Ok("tiles:admin.role.preadd")
	public Role rolePreAdd(@Param("roleid")String roleid){
		if(Strings.isEmpty(roleid)){
			return null;
		}else{
			return dao.fetch(Role.class,roleid);
		}
	}
	@At("/role/add")
	@Ok("redirect:/admin/role/manage")
	public void roleAdd(@Param("..")Role role){
		dao.insert(role);
	}
	@At("/role/update")
	@Ok("redirect:/admin/role/manage")
	public void roleUpdate(@Param("..")Role role){
		dao.update(role);
	}
	@At("/role/delete")
	@Ok("redirect:/admin/role/manage")
	public void roleDelete(@Param("ids")String[] roleids){
		if(roleids != null){
			for(String id: roleids){
				if(!Strings.isEmpty(id)){
					dao.clear(RoleUserRelation.class, Cnd.where("roleid","=",id));
					dao.delete(Role.class, id);
				}
			}
		}
	}
	@At("/vendor/manage")
	@Ok("tiles:admin.vendor.manage")
	public PageForm<Vendor> manageVendor(@Param("pageNum")int pageNum){
		
		PageForm<Vendor> pf = new PageForm<Vendor>();
		Pager page = dao.createPager(pageNum<1?1:pageNum, 20);
		List<Vendor> vendors = dao.query(Vendor.class, null, page);
		page.setRecordCount(dao.count(Vendor.class));
		pf.setPage(page);
		pf.setResultList(vendors);
		return pf;
	}
	@At("/vendor/preupdate")
	@Ok("tiles:admin.vendor.preupdate")
	public Vendor preUpdateVendor(@Param("vendorid")int vendorid){
		Vendor vendor= dao.fetch(Vendor.class,vendorid);
		return vendor;
	}
	@At("/vendor/update")
	@Ok("redirect:/admin/vendor/manage.do")
	public void updateVendor(@Param("::vendor." )Vendor vendor){
		Vendor vendorTemp= dao.fetch(Vendor.class,vendor.getId());
		vendor.setCreateTime(vendorTemp.getCreateTime());
		vendor.setUserid(vendorTemp.getUserid());
		vendor.setHomeUrl(vendorTemp.getHomeUrl());
		dao.update(vendor);
	}
	@At("/brand/manage")
	@Ok("tiles:admin.brand.manage")
	public PageForm<Brand> manageBrand(@Param("pageNum")int pageNum){
		Pager page= dao.createPager(pageNum<1?1:pageNum, 20);
		List<Brand> brands = dao.query(Brand.class, null, page);
		page.setRecordCount(dao.count(Brand.class));
		PageForm<Brand> pf = new PageForm<Brand>();
		pf.setPage(page);
		pf.setResultList(brands);
		return pf;
	}
	@At({"/brand/preupdate","/brand/preadd"})
	@Ok("tiles:admin.brand.preupdate")
	public Brand preUpdateBrand(@Param("brandid")int brandid){
		if(brandid!=0){
			return dao.fetch(Brand.class,brandid);
		}
		return null;
	}
	@At("/brand/update")
	@Ok("redirect:/admin/brand/manage")
	public void updateBrand(@Param("::brand.")Brand brand){
		if(brand.getId()==0){
			dao.insert(brand);
		}else{
			dao.update(brand);
		}
	}
	@At("/classify/manage")
	@Ok("tiles:admin.classify.manage")
	public List<Classify> manageClassify(@Param("pageNum")int pageNum){
		
		List<Classify> brands = dao.query(Classify.class, Cnd.wrap("order by classifyorder"), null);
		return brands;
	}
	@At("/classify/update")
	@Ok("redirect:/admin/classify/manage")
	public void updateClassify(@Param("classifys")String classifys){
		List<Classify> classifyList = new ArrayList<Classify>();
		int fromIndex = 0;
		int index = 0;
		while( (index = classifys.indexOf("}", fromIndex)) != -1){
			int beginIndex = classifys.indexOf("{",fromIndex);
			if(beginIndex!= -1){
				String classifyString = classifys.substring(beginIndex+1,index);
				String[] attrs = classifyString.split(",");
				Classify cly = new Classify();
				for(String attr : attrs){
					attr = attr.trim();
					if(attr.indexOf("id:")==0){
						cly.setId(Integer.valueOf(attr.substring(attr.indexOf("id:")+"id:".length())));
					}else if(attr.indexOf("classifyName:")==0){
						cly.setClassifyName(attr.substring(attr.indexOf("classifyName:")+"classifyName:".length()));
					}else if(attr.indexOf("classifyOrder:")==0){
						cly.setClassifyOrder(Short.valueOf(attr.substring(attr.indexOf("classifyOrder:")+"classifyOrder:".length())));
					}else if(attr.indexOf("parentid:")==0){
						cly.setParentid(Integer.valueOf(attr.substring(attr.indexOf("parentid:")+"parentid:".length())));
					}
				}
				classifyList.add(cly);
			}
			fromIndex = index+1;
		}
		List<Classify> classifyDb = dao.query(Classify.class, null, null);
		// delete the classify 
		if(classifyDb.size() !=0){
			for(Classify cdb : classifyDb){
				boolean result =false;
				for(Classify classify: classifyList){
					if(classify.getId()==cdb.getId()){
						result = true;
						break;
					}
				}
				if(!result){
					dao.delete(cdb);
				}
			}
		}
		// add the new classify and update the classify
		for(Classify classify : classifyList){
			if(0==classify.getId()){
				if(!Strings.isEmpty(classify.getClassifyName())){
					dao.insert(classify);
				}
			}else {
				if(!Strings.isEmpty(classify.getClassifyName())){
					dao.update(classify);
				}
			}
		}
		
	
	}
	@At("/product/manage")
	@Ok("tiles:admin.product.manage")
	public PageForm<Product> manageProduct(@Param("pageNum")int pageNum){
		Pager page = dao.createPager(pageNum<1?1:pageNum, 20);
		List<Product> products = dao.query(Product.class, null, page);
		page.setRecordCount(dao.count(Product.class));
		PageForm<Product> pf = new PageForm<Product>();
		pf.setPage(page);
		pf.setResultList(products);
		return pf;
	}
	@At("/product/delete")
	@Ok("redirect:/admin/product/manage.do")
	public void deleteProduct(@Param("ids")String[] ids){
		if(ids !=null && ids.length >0){
			for(String id : ids){
				if(!Strings.isEmpty(id)){
					dao.delete(Product.class,Long.valueOf(id));
				}
			}
		}
	}
	@At("/product/preupdate")
	@Ok("tiles:admin.product.preupdate")
	public ProductForm preUpdateProduct(@Param("productid")int productid){
		ProductForm pf = new ProductForm();
		List<Classify> classifys = dao.query(Classify.class, null,null);
		List<Brand> brands = dao.query(Brand.class,null,null);
		pf.setClassifys(classifys);
		pf.setBrands(brands);
		Product p = dao.fetch(Product.class,productid);
		pf.setProduct(p);
		return pf;
	}
	@At("/product/update")
	@Ok("redirect:/admin/product/manage")
	@AdaptBy(type=UploadAdaptor.class,args={"E:/TomcatShare/temp"})
	public void updateProduct(@Param("::product.")Product product,@Param("image")File image){
		if(product.getId()==0) return;
		if(image != null && !Strings.isEmpty(Files.getSuffixName(image))){
			if(!Strings.isEmpty(product.getImage()))
				Files.deleteFile(new File(ApplicationUtil.getWebHomePath()+product.getImage()));
			String newFilePath =  VendorHomeAction.IMAGE_UPLOAD_PATH+new StringGenerator(32, 32).next()+"."+Files.getSuffixName(image);
			log.debug("产品图片的url"+newFilePath);
			try {
				Files.copyFile(image, new File(ApplicationUtil.getWebHomePath()+newFilePath));
				product.setImage(newFilePath);
			} catch (IOException e) {
				log.error("产品上传图片出错了", e);
			}
		}
		dao.update(product);
	}
	@At("/system/manage")
	@Ok("tiles:admin.system.manage")
	public void systemManage(){
	}
	@At("/system/newsupload")
	@Ok("redirect:/admin/system/manage")
	@AdaptBy(type=UploadAdaptor.class,args={"E:/TomcatShare/temp"})
	public void newsUpload(@Param("image")File image,@Param("num")int num,HttpServletRequest req) throws IOException{
		if(num<1 || num >5){
			return ;
		}
		if(image != null && !Strings.isEmpty(Files.getSuffixName(image))){
			if(Files.getSuffixName(image).toLowerCase().equals("jpg")){
				Files.copyFile(image, new File(ApplicationUtil.getWebHomePath()+"/images/news_"+num+".jpg"));
				req.getSession().setAttribute("message", "上传成功");
			}else{
				req.getSession().setAttribute("message", "图片格式不对");
				return ;
			}
		}
	}
	@At("/system/create-static-home-page")
	@Ok("redirect:/admin/system/manage")
	public void createStaticHomePage(HttpServletRequest req) throws Exception{
		Map<String, Object> model = FreemarkerUtils.getInitMap();
		List<Classify> classifyList = dao.query(Classify.class, Cnd.wrap("1=1 order by parentid"), null);
		List<Brand> brandList = dao.query(Brand.class, null, null);
		// 生成随机的 产品index
		long productCount = dao.count(Product.class,Cnd.wrap("state = 1"));
		int productIndex = 0;
		if(productCount>8){
			Random r = new Random();
			productIndex = r.nextInt((int) (productCount-8));
		}
		List<Product> newProducts = dao.query(Product.class,Cnd.wrap("state = 1 limit "+productIndex+","+12), null);
		
		List<Product> recommendProducts = dao.query(Product.class,Cnd.wrap("state = 1 and isrecommend=1 limit 0,8"), null);
		List<Article> articles = dao.query(Article.class, Cnd.wrap("1=1 order by id desc limit 0,10"), null);
		List<NewsImage> newsImages= dao.query(NewsImage.class, Cnd.wrap("1=1 limit 0,5"), null);
		List<Pinpai> pinpais =dao.query(Pinpai.class, null, null);
		List<SpecialVendor> svendors = dao.query(SpecialVendor.class,null,null);
		
		model.put("classifys", classifyList.size()==0?null:classifyList);
		model.put("pinpais", pinpais.size()==0?null:pinpais);
		model.put("brands", brandList);
		model.put("newproducts", newProducts);
		model.put("recommendProducts", recommendProducts);
		model.put("newsimages", newsImages);
		model.put("articles", articles);
		model.put("svendors", svendors);
		model.put("contextPath", req.getContextPath());
		
		FreemarkerUtils.getInstance().mergeTemplateIntoHtml("WEB-INF/template/classify.ftl","/static/classify.html", model);
		FreemarkerUtils.getInstance().mergeTemplateIntoHtml("WEB-INF/template/brand.ftl","/static/brand.html", model);
		FreemarkerUtils.getInstance().mergeTemplateIntoHtml("WEB-INF/template/menu-brand.ftl","/static/menu-brand.html", model);
		FreemarkerUtils.getInstance().mergeTemplateIntoHtml("WEB-INF/template/pinpai.ftl","/static/pinpai.html", model);
		FreemarkerUtils.getInstance().mergeTemplateIntoHtml("WEB-INF/template/index.ftl","/index.shtml", model);
	}
}

